package concrete;

//import javax.swing.JOptionPane;

import frontend.BoardFrame;




/*  The Player class will serve as the template for players of the game, which will
    usually be the user/s  */
    
public class Player {


	//VARIABLES
	private String name;
	private Token token;
	private int cash;
	private Deed[] deeds = new Deed[30];
	private boolean inJail;
	private int tryDoubles;


	//CONSTRUCTORS
	public Player() {
		this.cash = 1500;
		this.inJail = false;
		this.tryDoubles = 0;
		initDeeds();
	}
	public Player(String name) {
		this.name = name;
		this.cash = 1500;
		this.inJail = false;
		this.tryDoubles = 0;
		initDeeds();
	}
	public Player(Token token) {
		this.token = token;
		this.cash = 1500;
		this.inJail = false;
		this.tryDoubles = 0;
		initDeeds();
	}
	public Player(String name, Token token) {
		this.name = name;
		this.token = token;
		this.cash = 1500;
		this.inJail = false;
		this.tryDoubles = 0;
		initDeeds();
	}


	//GETTERS
	public String getName() {
		return this.name;
	}
	public Token getToken() {
		return this.token;
	}
	public int getCash() {
		return this.cash;
	}
	public Deed getDeed(int num) {
		return this.deeds[num];
	}
	public boolean getInJail() {
		return this.inJail;
	}
	public int getTryDoubles() {
		return this.tryDoubles;
	}


	//SETTERS
	public void setName(String name) {
		this.name = name;
	}
	public void setToken(Token token) {
		this.token = token;
	}
	public void setCash(int cash) {
		this.cash = cash;
	}
	public void setDeed(Deed deed,int num) {
		this.deeds[num] = deed;
	}
	public void setInJail(boolean inJail) {
		this.inJail = inJail;
	}
	public void setTryDoubles(int tryDoubles) {
		this.tryDoubles = tryDoubles;
	}


	//OTHER METHODS
	//Methods used by the player to buy a property
	private void initDeeds() {
		for(int i=0; i<30; i++) {
			this.deeds[i] = null;
		}
	}
	
	public boolean buyEstate(Estate estate,int num) {
		estate.setPropertyOwner(this);
		this.identifyDeed(num);
		return true;
	}
	public boolean buyUtility(Utility utility,int num) {
		utility.setPropertyOwner(this);
		this.identifyDeed(num);
		return true;
	}
	public boolean buyStation(Station station,int num) {
		station.setPropertyOwner(this);
		this.identifyDeed(num);
		return true;
	}
	public void identifyDeed(int num) {
		if(1==num)
			this.acquireDeed(0);
		if(3==num)
			this.acquireDeed(1);
		if(6==num)
			this.acquireDeed(2);
		if(8==num)
			this.acquireDeed(3);
		if(9==num)
			this.acquireDeed(4);
		if(11==num)
			this.acquireDeed(5);
		if(13==num)
			this.acquireDeed(6);
		if(14==num)
			this.acquireDeed(7);
		if(16==num)
			this.acquireDeed(8);
		if(18==num)
			this.acquireDeed(9);
		if(19==num)
			this.acquireDeed(10);
		if(21==num)
			this.acquireDeed(11);
		if(23==num)
			this.acquireDeed(12);
		if(24==num)
			this.acquireDeed(13);
		if(26==num)
			this.acquireDeed(14);
		if(27==num)
			this.acquireDeed(15);
		if(29==num)
			this.acquireDeed(16);
		if(31==num)
			this.acquireDeed(17);
		if(32==num)
			this.acquireDeed(18);
		if(34==num)
			this.acquireDeed(19);
		if(37==num)
			this.acquireDeed(20);
		if(39==num)
			this.acquireDeed(21);
	}
	public void acquireDeed(int num) {
		this.deeds[num] = new Deed();
	}
	//Methods used by the player to pay rent
	public int computeEstateRent(Estate estate, int position) {
		int cost = estate.getRent();
		
		if(estate.getMonopoly()) {
			if(estate.getHouses()==0)
				cost = cost * 2;
			if(estate.getHouses()==1)
				cost = estate.getRentHouse1();
			if(estate.getHouses()==2)
				cost = estate.getRentHouse2();
			if(estate.getHouses()==3)
				cost = estate.getRentHouse3();
			if(estate.getHouses()==4) {
				if(!estate.getHotel())
					cost = estate.getRentHouse4();
				if(estate.getHotel())
					cost = estate.getRentHotel();
			}
		}
		
		return cost;
	}
	public void payEstateRent(Estate estate, int position) {
		int cost = this.computeEstateRent(estate, position);
		
		estate.getPropertyOwner().setCash(estate.getPropertyOwner().getCash() + cost);
		this.setCash(this.getCash() - cost);
	}
	public int computeUtilityRent(Utility utility, int num) {
		int cost = 0;
		if(utility.getMonopoly())
			cost = utility.getRentUtility2() * num;
		else
			cost = utility.getRent() * num;
		
		return cost;
	}
	public void payUtilityRent(Utility utility,int num) {
		//Count how many utilities do the property owner have
		int cost = this.computeUtilityRent(utility, num);
		
		utility.getPropertyOwner().setCash(utility.getPropertyOwner().getCash() + cost);
		this.setCash(this.getCash() - cost);
	}
	
	public int computeStationRent(Station station) {
		//Count how many Stations do the Property owner have
		int counter = 0;
		int cost = 0;

		if(null!=station.getPropertyOwner().getDeed(24))
			counter++;
		if(null!=station.getPropertyOwner().getDeed(25))
			counter++;
		if(null!=station.getPropertyOwner().getDeed(26))
			counter++;
		if(null!=station.getPropertyOwner().getDeed(27))
			counter++;

		if(1==counter)
			cost=station.getRent();
		if(2==counter)
			cost=station.getRentStation2();
		if(3==counter)
			cost=station.getRentStation3();
		if(4==counter)
			cost=station.getRentStation4();

		return cost;
	}
	public void payStationRent(Station station) {
		//Identifies how to pay station rent based on the number of stations owned by the landlord
		int cost = this.computeStationRent(station);
		
		station.getPropertyOwner().setCash(station.getPropertyOwner().getCash() + cost);
		this.setCash(this.getCash() - cost);

	}
	
	public void payCash(int pay) {
		this.setCash(this.getCash()-pay);
	}
	public void claimCash(int claim) {
		this.setCash(this.getCash()+claim);
	}
	public void postBail() {
		this.setCash(this.getCash()-50);
	}
	public void getSalary() {
		this.setCash(this.getCash()+200);
	}
	
	//Community Chest
	public void executeCommunity(BoardFrame boardFrame, int num) {
		
		boardFrame.setExecuteDeck(true);
		//Identifies Community Card function
		if(num==1) {
			this.payCash(100);
		}
		if(num==2) {
			this.payCash(10);
		}
		if(num==3 || num==4) {
			this.payCash(50);
		}
		if(num==5) {
			this.claimCash(200);
		}
		if(num==6) {
			this.claimCash(10);
		}
		if(num==7) {
			this.claimCash(20);
		}
		if(num==8) {
			this.claimCash(50);
		}
		if(num==9) {
			this.claimCash(25);
		}
		if(num==10 || num==11) {
			this.claimCash(100);
		}
		if(num==12) {
			int collect = 0;
			for(int i=0; i<boardFrame.getPlayerNum(); i++) {
				boardFrame.getPlayer(i).setCash(boardFrame.getPlayer(i).getCash()-10);
				collect+=10;
			}
			boardFrame.getCurrentPlayer().setCash(boardFrame.getCurrentPlayer().getCash()+collect);
		}
		if(num==13) {
			boardFrame.setDestination(40-boardFrame.getCurrentPlayer().getToken().getPosition());
			
			boardFrame.setCtr(0);
			boardFrame.setStep(1);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==14) {
			boardFrame.setDestination(1-boardFrame.getCurrentPlayer().getToken().getPosition());
			boardFrame.setStep(-1);
			boardFrame.setCtr(0);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==15) {
			this.executeChance(boardFrame, 14);
		}
		if(num==16) {
			this.deeds[29] = new Deed();
			boardFrame.getBoard().getContainer(2).getDeck().setGetOutJail(false);
		}
		boardFrame.setExecuteDeck(false);
	}
	public int computePropertyCost(BoardFrame boardFrame, Player player, int housePrice, int hotelPrice) {
		int cost = 0;
		int house = 0;
		int hotel = 0;
		
		if(null!=player.getDeed(0) && null!=player.getDeed(1)) {
			if(boardFrame.getBoard().getContainer(1).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(1).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(3).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(3).getEstate().getHouses();
		}
		if(null!=player.getDeed(2) && null!=player.getDeed(3) && null!=player.getDeed(4)) {
			if(boardFrame.getBoard().getContainer(6).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(6).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(8).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(8).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(9).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(9).getEstate().getHouses();
		}
		if(null!=player.getDeed(5) && null!=player.getDeed(6) && null!=player.getDeed(7)) {
			if(boardFrame.getBoard().getContainer(11).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(11).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(13).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(13).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(14).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(14).getEstate().getHouses();
		}
		if(null!=player.getDeed(8) && null!=player.getDeed(9) && null!=player.getDeed(10)) {
			if(boardFrame.getBoard().getContainer(16).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(16).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(18).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(18).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(19).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(19).getEstate().getHouses();
		}
		if(null!=player.getDeed(11) && null!=player.getDeed(12) && null!=player.getDeed(13)) {
			if(boardFrame.getBoard().getContainer(21).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(21).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(23).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(23).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(24).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(24).getEstate().getHouses();
		}
		if(null!=player.getDeed(14) && null!=player.getDeed(15) && null!=player.getDeed(16)) {
			if(boardFrame.getBoard().getContainer(26).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(26).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(27).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(27).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(29).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(29).getEstate().getHouses();
		}
		if(null!=player.getDeed(17) && null!=player.getDeed(18) && null!=player.getDeed(19)) {
			if(boardFrame.getBoard().getContainer(31).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(31).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(32).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(32).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(34).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(34).getEstate().getHouses();
		}
		if(null!=player.getDeed(20) && null!=player.getDeed(21)) {
			if(boardFrame.getBoard().getContainer(37).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(37).getEstate().getHouses();
			if(boardFrame.getBoard().getContainer(39).getEstate().getHotel())
				hotel = hotel + 1;
			else
				house = house + boardFrame.getBoard().getContainer(39).getEstate().getHouses();
		}
		int hotelCost = hotel * hotelPrice;
		int houseCost = house *housePrice;
		
		cost = hotelCost + houseCost;
		return cost;
	}
	//Chance Cards
	public void executeChance(BoardFrame boardFrame, int num) {
		
		boardFrame.setExecuteDeck(true);
		//Identify the appropriate chance card function
		if(num==1) {
			//this.setCash(this.cash - 15);
			this.payCash(15);
		}
		if(num==2) {
			this.payCash(150);
		}
		if(num==3) {
			this.payCash(20);
		}
		if(num==4) {
			this.claimCash(50);
		}
		if(num==5) {
			this.claimCash(150);
		}
		if(num==6) {
			this.claimCash(100);
		}
		if(num==7) {
			this.payCash(this.computePropertyCost(boardFrame, this, 25, 100));
			//JOptionPane.showMessageDialog(null,"The features needed to implement this\nChance Card is not yet available","Under Construction",JOptionPane.PLAIN_MESSAGE);
		}
		if(num==8) {
			this.payCash(this.computePropertyCost(boardFrame, this, 40, 115));
			//JOptionPane.showMessageDialog(null,"The features needed to implement this\nChance Card is not yet available","Under Construction",JOptionPane.PLAIN_MESSAGE);
		}
		if(num==9) {
			if(24>boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setDestination(24-boardFrame.getCurrentPlayer().getToken().getPosition());

			if(24<boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setDestination(64-boardFrame.getCurrentPlayer().getToken().getPosition());

			boardFrame.setCtr(0);
			boardFrame.setStep(1);
			//boardFrame.setExecuteDeck(true);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==10) {
			boardFrame.setDestination(40-boardFrame.getCurrentPlayer().getToken().getPosition());
			
			boardFrame.setCtr(0);
			boardFrame.setStep(1);
			//boardFrame.setExecuteDeck(true);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==11) {
			boardFrame.setDestination(39-boardFrame.getCurrentPlayer().getToken().getPosition());
			
			boardFrame.setCtr(0);
			boardFrame.setStep(1);
			//boardFrame.setExecuteDeck(true);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==12) {
			if(11>boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setDestination(11-boardFrame.getCurrentPlayer().getToken().getPosition());

			if(11<boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setDestination(51-boardFrame.getCurrentPlayer().getToken().getPosition());

			boardFrame.setCtr(0);
			boardFrame.setStep(1);
			//boardFrame.setExecuteDeck(true);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==13) {
			if(15>boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setDestination(15-boardFrame.getCurrentPlayer().getToken().getPosition());

			if(15<boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setDestination(55-boardFrame.getCurrentPlayer().getToken().getPosition());

			boardFrame.setCtr(0);
			boardFrame.setStep(1);
			//boardFrame.setExecuteDeck(true);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==14) {
			if(10>boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setStep(1);

			if(10<boardFrame.getCurrentPlayer().getToken().getPosition())
				boardFrame.setStep(-1);

			this.inJail = true;
			boardFrame.setDestination(10-boardFrame.getCurrentPlayer().getToken().getPosition());
			boardFrame.setCtr(0);
			//boardFrame.setExecuteDeck(true);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==15) {
			
			boardFrame.setStep(-1);
			boardFrame.setDestination(-3);
			boardFrame.setCtr(0);
			//boardFrame.setExecuteDeck(true);
			boardFrame.setIsRunning(true);
			boardFrame.setGotoJail(true);
		}
		if(num==16) {
			this.deeds[28] = new Deed();
			boardFrame.getBoard().getContainer(7).getDeck().setGetOutJail(false);
		}
		
		boardFrame.setExecuteDeck(false);
	}
	
	public void returnDeeds(Board board) {
		if(null!=this.deeds[0]) {
			board.getContainer(1).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[1]) {
			board.getContainer(3).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[2]) {
			board.getContainer(6).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[3]) {
			board.getContainer(8).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[4]) {
			board.getContainer(9).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[5]) {
			board.getContainer(11).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[6]) {
			board.getContainer(13).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[7]) {
			board.getContainer(14).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[8]) {
			board.getContainer(16).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[9]) {
			board.getContainer(18).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[10]) {
			board.getContainer(19).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[11]) {
			board.getContainer(21).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[12]) {
			board.getContainer(23).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[13]) {
			board.getContainer(24).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[14]) {
			board.getContainer(26).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[15]) {
			board.getContainer(27).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[16]) {
			board.getContainer(29).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[17]) {
			board.getContainer(31).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[18]) {
			board.getContainer(32).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[19]) {
			board.getContainer(34).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[20]) {
			board.getContainer(37).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[21]) {
			board.getContainer(39).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[22]) {
			board.getContainer(12).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[23]) {
			board.getContainer(28).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[24]) {
			board.getContainer(5).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[25]) {
			board.getContainer(15).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[26]) {
			board.getContainer(25).getEstate().setPropertyOwner(null);
		}
		if(null!=this.deeds[27]) {
			board.getContainer(35).getEstate().setPropertyOwner(null);
		}
	}
}